#include "mkvstreamaudio.hpp"
#include "mkvcontext.hpp"

class CMediaTypes;

namespace VorbisTypes
{
struct VORBISFORMAT2;
}

namespace MkvMux
{

class MkvStreamAudioVorbis : public MkvStreamAudio
{
    MkvStreamAudioVorbis(const MkvStreamAudioVorbis&);
    MkvStreamAudioVorbis& operator=(const MkvStreamAudioVorbis&);
    
protected:
    MkvStreamAudioVorbis(MkvContext&, const BYTE*, ULONG);    

    ULONG GetSamplesPerSec() const;
    BYTE GetChannels() const;

    void WriteTrackCodecID();
    void WriteTrackCodecName();
    void WriteTrackCodecPrivate();

public:
    static void GetMediaTypes(CMediaTypes&);
    static bool QueryAccept(const AM_MEDIA_TYPE&);
    //static bool OnReceiveConnection(const AM_MEDIA_TYPE&);

    static HRESULT GetAllocatorRequirements(
                    const AM_MEDIA_TYPE&,
                    ALLOCATOR_PROPERTIES&);

    static MkvStreamAudio* CreateStream(MkvContext&, const AM_MEDIA_TYPE&);

    HRESULT Receive(IMediaSample*);
    int EndOfStream();

private:
    const VorbisTypes::VORBISFORMAT2& GetFormat() const;

    class VorbisFrame : public AudioFrame
    {
        VorbisFrame& operator=(const VorbisFrame&);
        VorbisFrame(const VorbisFrame&);
      
    private:
        IMediaSample* const m_pSample;

    public:
        explicit VorbisFrame(IMediaSample*);
        ~VorbisFrame();

        ULONG curr_timecode_ms() const;

        ULONG size() const;
        const BYTE* data() const;
      
    };
    
};

}  //end namespace MkvMux
